﻿using System;
using System.Collections.Generic;
using System.Linq;
using System.Reflection;
using System.Text;
using System.Threading.Tasks;
using System.Windows;

namespace MyMusicPlay._4._0
{
    using Elements = Dictionary<Type, Dictionary<string, List<FrameworkElement>>>;
    using ElementFactorys = Dictionary<string, ElementFactoryBase>;//Key:元素的名称
    public class ElementFactoryBase : BaseClass
    {
        protected MainWindow _mainWindow;

        /// <summary>
        /// 总创建元素集合
        /// </summary>
        private Elements ElementAllCreateList = new();

        /// <summary>
        /// 元素对应工厂集合
        /// </summary>
        private ElementFactorys ElementFactoryList = new();

        public ElementFactoryBase(MainWindow main)
        {
            _mainWindow = main;
        }

        public void Initialize()
        {
            foreach (var item in Assembly.GetExecutingAssembly().GetTypes())
            {
                if (this.GetType().IsAssignableFrom(item))
                {
                    if (item.Name != this.GetType().Name)
                    {
                        var obj = CreateFactory(item);
                        ElementFactoryList.Add(item.Name.Replace("Factory", ""), obj);
                    }
                }
            }
            InitializeElement();
        }



        #region 对元素的操作
        /// <summary>
        /// 添加
        /// </summary>
        /// <param name="IsUpdateColor">是否需要放到修改颜色的集合中</param>
        public void Add(FrameworkElement frameworkElement, bool IsUpdateColor)
        {
            var name = frameworkElement.Name ?? "";
            var elmType = frameworkElement.GetType();
            Dictionary<string, List<FrameworkElement>> elmList;
            if (!ElementAllCreateList.ContainsKey(elmType))
            {
                var newList = new Dictionary<string, List<FrameworkElement>>();
                newList.Add("UpdateColor", new List<FrameworkElement>());
                ElementAllCreateList.Add(elmType, newList);
            }
            elmList = ElementAllCreateList[elmType];

            if (!elmList.ContainsKey(name))
            {
                elmList.Add(name, new List<FrameworkElement>());
            }
            elmList[name].Add(frameworkElement);
            if (IsUpdateColor)
                elmList["UpdateColor"].Add(frameworkElement);
        }

        /// <summary>
        /// 使用指定工厂创建元素
        /// </summary>
        /// <typeparam name="T">工厂类型</typeparam>
        /// <typeparam name="Element">创建元素类型</typeparam>
        /// <param name="act">元素对应的字段赋值</param>
        /// <returns>创建元素[已加入元素集合]</returns>
        public Element Create<Element>(Action<Element> act = null, bool IsFactory = true, bool IsUpdateColor = false)
            where Element : FrameworkElement, new()
        {
            Element element;
            //查找对应工厂
            if (IsFactory && ElementFactoryList.ContainsKey(typeof(Element).Name))
            {
                dynamic factory = ElementFactoryList[typeof(Element).Name];
                element = (factory.CreateElement<Element>(act) as Element)!;
            }
            else
            {
                element = this.CreateElement<Element>(act);
            }
            Add(element, IsUpdateColor);
            return element;
        }

        public List<FrameworkElement> Remove<T>(string name) where T : FrameworkElement
        {
            if (ElementAllCreateList.ContainsKey(typeof(T)))
            {
                if (ElementAllCreateList[typeof(T)].ContainsKey(name))
                {
                    var cur = ElementAllCreateList[typeof(T)][name];
                    ElementAllCreateList[typeof(T)].Remove(name);
                    return cur;
                }
            }
            return null;
        }

        public List<FrameworkElement> Get<T>(string name) where T : FrameworkElement
        {
            if (ElementAllCreateList.ContainsKey(typeof(T)))
            {
                if (ElementAllCreateList[typeof(T)].ContainsKey(name))
                {
                    return ElementAllCreateList[typeof(T)][name];
                }
            }
            return null;
        }

        /// <summary>
        /// 创建元素对象[如果没有对应的元素工厂则返回NULL][创建工厂必须遵循 元素Name+Factory ]
        /// </summary>
        protected virtual Element CreateElement<Element>(Action<Element> action = null)
            where Element : FrameworkElement, new()
        {
            Element element = new();
            if (action != null)
                action(element);
            return element;
        }
        #endregion

        #region 对工厂的操作
        private ElementFactoryBase CreateFactory(Type type)
            => Activator.CreateInstance(type, _mainWindow) as ElementFactoryBase;

        #endregion

        #region Tool
        /// <summary>
        /// 获取修改元素的集合
        /// </summary>
        public List<FrameworkElement> GetUpdateList<Element>() where Element : FrameworkElement
        {
            if (ElementAllCreateList.ContainsKey(typeof(Element)))
            {
                return ElementAllCreateList[typeof(Element)]["UpdateColor"];
            }
            return new List<FrameworkElement>();
        }
        #endregion

        //将写出来的元素注册到集合
        private void InitializeElement()
        {
            Add(_mainWindow.LoadBut, true);
            Add(_mainWindow.ConfigureBut, true);
            Add(_mainWindow.RetrievalBut, true);
            Add(_mainWindow.OpenDisplayViewBut, true);
            Add(_mainWindow.ShrinkBut, true);
            Add(_mainWindow.ShutdownBut, true);
            Add(_mainWindow.MusicDisplayList, true);
            Add(_mainWindow.PreviousBut, true);
            Add(_mainWindow.PlayingBut, true);
            Add(_mainWindow.NextBut, true);
            Add(_mainWindow.CurOrderState, true);

        }
    }
}
